package com.csyf.manager.controller.api;

import com.alibaba.fastjson.JSONObject;
import com.csyf.manager.channel.base.*;
import com.csyf.manager.entity.SysPayment;
import com.csyf.manager.entity.SysTrade;
import com.csyf.manager.exception.ApiValidateException;
import com.csyf.manager.service.OrderBiz;
import com.csyf.manager.service.OrderService;
import com.csyf.manager.service.PayMentBiz;
import com.csyf.manager.service.impl.SysAgentBalanceBiz;
import com.csyf.manager.utils.IpHelper;
import com.csyf.manager.utils.NumberHelpler;
import com.csyf.manager.utils.SignUtils;
import com.google.gson.Gson;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.builder.ReflectionToStringBuilder;
import org.springframework.beans.NotReadablePropertyException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.validation.BindingResult;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import javax.validation.Valid;
import java.math.BigDecimal;
import java.util.HashMap;
import java.util.Map;

/**
 * @Author: Enzo
 * @Date: 2018/3/29 16:46
 */
@Slf4j
@Controller
@RequestMapping(value = "/pay/v2/")
public class ApiController extends ApiBaseController {


    @Autowired
    private OrderBiz orderBiz;


    @Autowired
    private OrderService orderService;

    @Autowired
    private PayMentBiz payMentBiz;


    @Autowired
    private SysAgentBalanceBiz sysAgentBalanceBiz;


    @ExceptionHandler
    @ResponseBody
    @RequestMapping(value = "orderPay")
    public BaseReturn transRequest(@Validated TrandeVo vo, BindingResult bindingResult, HttpServletRequest request) {


        try {


            validateHibernate(bindingResult);
            String ipAddr = IpHelper.getIpAddr(request);

            log.info("[{}]，支付IP[{}]，接受参数:{}", vo.getOut_trade_no(), ipAddr, ReflectionToStringBuilder.toString(vo));

            validateTradeWhileIp(ipAddr, vo.getMch_id());

            validmerchid(vo.getMch_id());

            validservice(vo.getMch_id(), vo.getService());

            validatetotalFree(vo.getTotal_fee(), vo.getService());

            validServiceParam(vo);

            validsign(vo, vo.getMch_id(), vo.getSign());


            String order = orderBiz.createOrder(vo);
            PayInfoReturn payInfoReturn = new PayInfoReturn();
            payInfoReturn.setPayinfo(order);
            payInfoReturn.setRet_code("SUCCESS");
            payInfoReturn.setOrderNo(vo.getOut_trade_no());
            payInfoReturn.setRet_message("请求成功");
            payInfoReturn.setMch_id(vo.getMch_id());
            payInfoReturn.setTotal_fee(vo.getTotal_fee());
            String sign = SignUtils.objectsign(payInfoReturn, getAgentSignKey(vo.getMch_id()));

            payInfoReturn.setSign(sign);

            log.info("[{}]支付订单号返回下游参数payinfo{}", vo.getOut_trade_no(), order);
            return payInfoReturn;
        } catch (ApiValidateException e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message(e.getMessage());
            orderBiz.orderFaile(vo.getOut_trade_no(), "9998", e.getMessage());
            return baseReturn;
        } catch (IllegalArgumentException e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message(e.getMessage());
            return baseReturn;
        } catch (NotReadablePropertyException e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message("请求方式不正确");
            return baseReturn;
        } catch (Exception e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message(e.getMessage());
            log.error("", e);
            return baseReturn;
        }
    }


    @ResponseBody
    @RequestMapping(value = "transferPay")
    public BaseReturn dftransRequest(@Validated PaymentVo vo, BindingResult bindingResult, HttpServletRequest request) {


        try {

            validateHibernate(bindingResult);
            String ipAddr = IpHelper.getIpAddr(request);

            log.info("[{}]，代付IP[{}]，接受参数:{}", vo.getOut_trade_no(), ipAddr, ReflectionToStringBuilder.toString(vo));

            validmerchid(vo.getMch_id());

            validservice(vo.getMch_id(), vo.getService());

            validatePaymentWhileIp(ipAddr, vo.getMch_id());

            validatePaymentBankCard(vo.getBank_card(), vo.getMch_id());

            validsign(vo, vo.getMch_id(), vo.getSign());

            validDfServiceParam(vo);

            Map<String, String> createorder = payMentBiz.createorder(vo);

            PaymentReturn payInfoReturn = new PaymentReturn();
            payInfoReturn.setTradeStatus(createorder.get("code"));
            payInfoReturn.setTradeMessage(createorder.get("message"));
            payInfoReturn.setRet_code("SUCCESS");
            payInfoReturn.setOrderNo(vo.getOut_trade_no());
            payInfoReturn.setTotal_fee(vo.getTrans_money());
            payInfoReturn.setMch_id(vo.getMch_id());
            payInfoReturn.setRet_message("请求成功");
            String objectsign1 = SignUtils.objectsign(payInfoReturn, getAgentSignKey(vo.getMch_id()));

            payInfoReturn.setSign(objectsign1);
            return payInfoReturn;
        } catch (ApiValidateException | IllegalArgumentException e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message(e.getMessage());
            log.info("[{}]返回信息{}", vo.getOut_trade_no(), new Gson().toJson(baseReturn));
            return baseReturn;
        } catch (NotReadablePropertyException e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message("请求方式不正确");
            e.printStackTrace();
            return baseReturn;
        } catch (Exception e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message(e.getMessage());
            e.printStackTrace();
            return baseReturn;
        }
    }


    @ResponseBody
    @RequestMapping(value = "orderQuery")
    public BaseReturn tradeQuery(@Valid BaseQuestVo vo, BindingResult bindingResult) {


        try {

            validateHibernate(bindingResult);

            validmerchid(vo.getMch_id());

            validsign(vo, vo.getMch_id(), vo.getSign());


            SysTrade sysTrade = orderService.queryOrderByOrderNo(vo.getMch_id(), vo.getOut_trade_no());


            if (null == sysTrade) {
                BaseReturn baseReturn = new BaseReturn();
                baseReturn.setRet_code("FAIL");
                baseReturn.setRet_message("订单不存在");
                return baseReturn;
            }


            QueryTeturnVo baseQuestVo = new QueryTeturnVo();
            baseQuestVo.setRet_code("SUCCESS");
            baseQuestVo.setRet_message("查询成功");
            baseQuestVo.setOrderNo(vo.getOut_trade_no());
            baseQuestVo.setTotal_fee(NumberHelpler.money2cent(sysTrade.getTotalFee()).toString());
            baseQuestVo.setPayStatus(sysTrade.getTradeStatus());
            baseQuestVo.setMch_id(vo.getMch_id());
            String objectsign1 = SignUtils.objectsign(baseQuestVo, getAgentSignKey(vo.getMch_id()));

            baseQuestVo.setSign(objectsign1);
            return baseQuestVo;


        } catch (ApiValidateException e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message(e.getMessage());
            return baseReturn;
        } catch (Exception e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message(e.getMessage());
            e.printStackTrace();
            return baseReturn;
        }

    }


    @ResponseBody
    @RequestMapping(value = "transferQuery")
    public BaseReturn dftradeQuery(@Valid BaseQuestVo vo, BindingResult bindingResult) {


        try {

            validateHibernate(bindingResult);

            validmerchid(vo.getMch_id());

            validsign(vo, vo.getMch_id(), vo.getSign());


            SysPayment sysPayment = payMentBiz.queryPaymentByOrderNo(vo.getMch_id(), vo.getOut_trade_no());

            if (null == sysPayment) {
                BaseReturn baseReturn = new BaseReturn();
                baseReturn.setRet_code("FAIL");
                baseReturn.setRet_message("订单不存在");
                return baseReturn;
            }

            log.info("[{}]商户查询订单号=[{}],订单状态=[{}]", vo.getMch_id(), vo.getOut_trade_no(), sysPayment.getPayStatus());

            String payMsg = sysPayment.getSrcReason();
            String payStatus = sysPayment.getPayStatus();

            if ("3".equals(payStatus)) {
                payMsg = "代付成功";
            } else if ("1".equals(payStatus)) {
                payMsg = "代付处理中";
            }

            QueryTeturnVo baseQuestVo = new QueryTeturnVo();
            baseQuestVo.setRet_code("SUCCESS");
            baseQuestVo.setRet_message("查询成功");
            baseQuestVo.setOrderNo(vo.getOut_trade_no());
            baseQuestVo.setPayStatus(sysPayment.getPayStatus());
            baseQuestVo.setPayMsg(payMsg == null ? "" : payMsg);
            baseQuestVo.setTotal_fee(NumberHelpler.money2cent(sysPayment.getTransmoney()).toString());
            baseQuestVo.setMch_id(vo.getMch_id());
            String objectsign1 = SignUtils.objectsign(baseQuestVo, getAgentSignKey(vo.getMch_id()));

            baseQuestVo.setSign(objectsign1);
            return baseQuestVo;


        } catch (ApiValidateException e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message(e.getMessage());
            return baseReturn;
        } catch (Exception e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message(e.getMessage());
            e.printStackTrace();
            return baseReturn;
        }

    }


    @ResponseBody
    @RequestMapping(value = "balanceQuery")
    public BaseReturn tradequery(@Valid BaseQuestVo vo, BindingResult bindingResult) {

        try {
            validateHibernate(bindingResult);

            validmerchid(vo.getMch_id());

            validsign(vo, vo.getMch_id(), vo.getSign());

            String service = vo.getService();
            BigDecimal balance = BigDecimal.ZERO;
            BigDecimal dzbalance = BigDecimal.ZERO;

            BalanceReturn balanceReturn = new BalanceReturn();
            balanceReturn.setMch_id(vo.getMch_id());
            balanceReturn.setRet_code("SUCCESS");
            if (StringUtils.isBlank(service)) {
                BaseReturn baseReturn = new BaseReturn();
                baseReturn.setRet_code("FAIL");
                baseReturn.setRet_message("请输入交易类型");
                log.error("余额查询:{}", "没有输入交易类型");
                return baseReturn;
            } else {
                String merchantNo = vo.getMch_id();
//
                balance = sysAgentBalanceBiz.queryBalance(merchantNo, service);
                dzbalance = sysAgentBalanceBiz.queryDzBalance(merchantNo, service);


            }

            balanceReturn.setCashbalance(NumberHelpler.money2cent(dzbalance));
            balanceReturn.setRestbalance(NumberHelpler.money2cent(balance));
            balanceReturn.setTotalbalance(NumberHelpler.money2cent(balance) + NumberHelpler.money2cent(dzbalance));
            String sign = SignUtils.objectsign(balanceReturn, getAgentSignKey(vo.getMch_id()));
            balanceReturn.setSign(sign);
            return balanceReturn;
        } catch (ApiValidateException e) {
            BaseReturn baseReturn = new BaseReturn();
            baseReturn.setRet_code("FAIL");
            baseReturn.setRet_message(e.getMessage());
            log.error("余额查询:{}", e.getMessage());
            return baseReturn;
        }
    }

    /**
     * 根据用户订单号查询订单商品名称、订单金额、订单号
     */
    @ResponseBody
    @RequestMapping(value = "getOrderInfo", method = RequestMethod.GET)
    public Map<String, Object> getOrderInfo(@RequestParam(value = "outTradeNo") String outTradeNo) {

        Map<String, Object> returnMap = new HashMap<>(3);

        if (org.apache.commons.lang.StringUtils.isBlank(outTradeNo)) {
            returnMap.put("code", "F001");
            returnMap.put("msg", "订单号不能为空");
            return returnMap;
        }

        SysTrade trade = orderService.queryOrderByOrderNo(outTradeNo);
        if (null == trade) {
            returnMap.put("code", "F002");
            returnMap.put("msg", "订单号不存在");
            return returnMap;
        }

        JSONObject jsonObject = new JSONObject();
        jsonObject.put("body", "交易");
        jsonObject.put("totalFee", trade.getTotalFee());
        jsonObject.put("outTradeNo", trade.getOutTradeNo());
        jsonObject.put("orderStatus", trade.getTradeStatus());
        jsonObject.put("srcMchId", trade.getSrcMchId());

        returnMap.put("code", "0000");
        returnMap.put("msg", "查询成功");
        returnMap.put("data", jsonObject);
        return returnMap;
    }
}
